#include "cbuffer.h"
#include <iostream>
#include "cpart.h"

CBuffer::CBuffer()
{
	NowIn=0;
	setType(CElement::TYPE_BUFFER);
	isEmpty=true;
	isFull=false;
	Capacity=10;
}

CBuffer::~CBuffer()
{
	Content.clear();
}

void CBuffer::Respond(CEvent* evt)
{
	
}

bool CBuffer::GetAPartIn(CPart* part)
{
	//
	if(part!=(CPart*)NULL)
	{
		Content.push_back(part);
		NowIn++;
		if(NowIn>=Capacity)
		{
			isFull=true;
		}
		isEmpty=false;
		return true;
	}
	return false;
}

CPart* CBuffer::GiveAPartOut()//先进先出
{
	CPart* p=(CPart*)NULL;
	if(NowIn>0)
	{
		std::vector<CPart*>::iterator it=Content.begin();
		p=(*it);
		Content.erase(it);
		NowIn--;
		if(NowIn<1)
		{
			isEmpty=true;
		}
		if(p!=(CPart*)NULL)
		{
			isFull=false;
		}
	}
	else
	{
		//
	}
	return p;
}


bool CBuffer::IsEmpty()
{
	return isEmpty;
}

bool CBuffer::IsFull()
{
	return isFull;
}

void CBuffer::setCapacity(int cp)
{
	Capacity=cp;
}

void CBuffer::showContent()
{
	std::cout<<"\nParts in Buffer:"<<std::endl;
	std::cout<<"FinalType\t\tDueTime\t\tCompleteTime"<<std::endl;
	std::vector<CPart*>::iterator it=Content.begin();
	for(;it!=Content.end();it++)
	{
		std::cout<<"\t"<<(*it)->getFinalType()<<"\t\t"<<(*it)->getDueTime()<<"\t\t"<<(*it)->getLastOpTime()<<std::endl;
	}
	std::cout<<"-------------------------------------------"<<std::endl;
	//std::cout<<"DELTA Td="<<
}

#include "lib.h"
#include <algorithm>
#include <iterator>
#include <math.h>


bool compare(const double first, const double second)
{
	if(first<second)
	{
		return true;
	}
	else{
		return false;
	}
}

double CBuffer::showDeltaTd(bool show_on_screen)
{
	double rs=0;

	std::vector<double> DueTimeSeries;
	std::vector<double> CompleteTimeSeries;
	for(int c=1;c<=C_out;c++)
	{
		DueTimeSeries.clear();
		CompleteTimeSeries.clear();
		std::vector<CPart*>::iterator it=Content.begin();
		for(;it!=Content.end();it++)
		{
			if((*it)->getFinalType()==c)
			{
				DueTimeSeries.push_back((*it)->getDueTime());
				CompleteTimeSeries.push_back((*it)->getLastOpTime());				
			}
		}
		//sort and sum
		sort(DueTimeSeries.begin(),DueTimeSeries.end(),compare);
		sort(CompleteTimeSeries.begin(),CompleteTimeSeries.end(),compare);
		std::vector<double>::iterator itD=DueTimeSeries.begin();
		std::vector<double>::iterator itC=CompleteTimeSeries.begin();
		for(;itD!=DueTimeSeries.end() && itC!=CompleteTimeSeries.end();)
		{
			rs=rs+fabs((*itD)-(*itC));
			//////////////
			itD++;
			itC++;
		}
	}
	if(show_on_screen){
		std::cout<<"********************************\n********  Delta Td = "<<rs<<"\n*************************"<<std::endl;
	}
	return rs;
}

double CBuffer::showW_sigma(double start_time,double end_time,double alpha, double beta,bool show_on_screen)
	//show the weighted sum of earliness and tardiness accord to a common due window
{
	double rs=0.0;
	std::vector<CPart*>::iterator it=Content.begin();
	for(;it!=Content.end();it++)
	{
		double tt=(*it)->getLastOpTime();
		if(tt<start_time)
		{
			rs=rs+alpha*(start_time-tt);
		}
		else if(tt>end_time)
		{
			rs=rs+beta*(tt-end_time);
		}
	}
	if(show_on_screen)
	{
		std::cout<<"W(sigma)="<<rs<<std::endl;
	}
	return rs;
}